﻿Public Class Writer

    Public Sub writeHtml(title As String, doc As Object, path As String)
        Dim newBook As HtmlWriter = New HtmlWriter(title, path)

        Dim linesWritten As Integer = 0
        Dim titleType As Integer = -1
        ' Strings for title filtering
        Dim title1 As String = "Inhaltsverzeichnisüberschrift"
        Dim title2 As String = "Überschrift 2"
        Dim titlesPerPage As Integer = 0
        Dim additionalChars As Integer = 0

        ' iterate paragraphs of document
        For Each paragraph As MyParagraph In doc.paragraphs

            ' create new string for words of paragraph
            Dim newWordString As String = ""

            ' empty paragraph is empty line -> write
            If paragraph.empty Then
                ' write empty line
                newBook.writeLineBrake()
                linesWritten += 2
                ' if paragraph empty go to next paragraph
                Continue For
            End If

            Dim curFormat As MyFormat

            ' iterate sentences of paragraph
            For Each sentence As MySentence In paragraph.sentences

                curFormat = doc.globalFormats(sentence.commonFormat)

                ' Check for titles, they have to be written using writeTitle instead of writeText and also do not need any kind of special format handling stuff
                ' Necessary for table of contents generation
                If curFormat.formatName = title1 Then
                    'newBook.writeTitle()
                    titleType = 0
                ElseIf curFormat.formatName = title2 Then
                    'newBook.writeTitle()
                    titleType = 1
                End If
                ' No title but regular text
                ' Check if sentence has any kind of special format or just one single format
                Dim easySentence As Boolean = False
                If sentence.specialFormat.Count = 0 Then easySentence = True

                ' iterate words of sentence
                For i = 0 To sentence.words.Length - 1

                    'check for maximum of lines per page
                    If linesWritten >= 27 Then
                        newBook.nextPage()
                        linesWritten = 0
                        titlesPerPage = 0
                        additionalChars = 0
                    End If

                    ' if is empty -> no word but special character
                    If sentence.words(i) Is "" Then
                        ' special char handling
                        If sentence.specialChars(i) = "<TAB>" Then
                            ' special char is tab, write string to file, use insert tab function and reset word
                            newBook.writeText(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                            newBook.writeTab()
                            ' ToDo: check if reseting string this way works or is memory leak - delete object necessary or way done is sufficient
                            newWordString = ""
                            additionalChars += 6
                        ElseIf sentence.specialChars(i) = "<BR>" Then
                            ' special char is special line break
                            newBook.writeText(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                            newBook.writeLineBrake()
                            linesWritten += calcLines(curFormat.size)
                            newWordString = ""
                            additionalChars = 0
                        End If
                    ElseIf Not easySentence And sentence.specialFormat.ContainsKey(i) Then
                        ' sentence containing specially formatted words and current word is specially formatted
                        'write string to file and reset word
                        newBook.writeText(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                        additionalChars += newWordString.Length
                        newWordString = ""
                        'get format of special word
                        Dim specFormat As MyFormat = doc.globalFormats(sentence.specialFormat.Item(i))
                        'write special word to file
                        newBook.writeText(sentence.words(i), calcHtmlOutputFont(specFormat.size), specFormat.colorCode, specFormat.font, specFormat.bold, specFormat.italic, specFormat.underlined)
                        additionalChars += sentence.words(i).Length
                    Else
                        ' check for empty strings first
                        If sentence.words(i).StartsWith(" ") Then
                            For j = 0 To sentence.words(i).Length
                                newBook.writeSpace()
                            Next
                            additionalChars += sentence.words(i).Length
                        End If
                        ' regular word string, may be regular text or title
                        If newWordString Is "" Then
                            newWordString += sentence.words(i)
                        Else
                            ' too long for one line
                            If (newWordString.Length + sentence.words(i).Length + additionalChars) > lineLength(curFormat.size) Then
                                newBook.writeText(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                                newBook.writeLineBrake()
                                linesWritten += calcLines(curFormat.size)
                                newWordString = sentence.words(i)
                                additionalChars = 0
                            Else
                                ' newWordString += " "
                                newWordString += sentence.words(i)
                            End If
                        End If
                    End If
                Next
            Next

            ' paragraph done -> write string and zeilenumbruch
            ' check whether title or regular text
            If titleType < 0 Then
                ' if < 0 no title in current paragraph
                newBook.writeText(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                linesWritten += calcLines(curFormat.size)
                newBook.writeLineBrake()
                additionalChars = 0
            Else
                ' if >= 0 title type contains type of title to write
                If titlesPerPage > 0 Then
                    newBook.newTitleatTheSameSide()
                End If
                newBook.writeTitle(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined, titleType)
                titlesPerPage += 1
                linesWritten += calcLines(curFormat.size)
                newBook.writeLineBrake()
                titleType = -1
                additionalChars = 0
            End If

        Next

        ' ToDo where and how is new page saved, appropriate place to insert new page needs to be determined
        ' Not possible

        'finish book
        newBook.finishBook()


    End Sub

    Public Sub writeEPub(title As String, doc As Object, path As String)
        'create new epub creator
        Dim newBook As EpubCreator = New EpubCreator(title, path)


        ' iterate paragraphs of document
        For Each paragraph As MyParagraph In doc.paragraphs

            ' create new string for words of paragraph
            Dim newWordString As String = ""

            ' empty paragraph is empty line -> write
            If paragraph.empty Then
                ' write empty line
                newBook.writeBlankLine()
                ' if paragraph empty go to next paragraph
                Continue For
            Else
                'paragraph not empty -> start new one
                newBook.OpenParagraph()
            End If

            Dim curFormat As MyFormat

            ' iterate sentences of paragraph
            For Each sentence As MySentence In paragraph.sentences

                curFormat = doc.globalFormats(sentence.commonFormat)

                ' ToDo: Ask Daniel how empty special formats = sentence without special stuff is saved technically, via nothing oder empty dict ?
                Dim easySentence As Boolean = False
                If sentence.specialFormat.Count = 0 Then easySentence = True

                ' iterate words of sentence
                For i = 0 To sentence.words.Length - 1
                    ' if is nothing -> no word but special character
                    If sentence.words(i) Is Nothing Then
                        ' special char handling
                        If sentence.specialChars(i) = "<TAB>" Then
                            ' special char is tab, write string to file, use insert tab function and reset word
                            'newBook.writeTexte(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                            newBook.writeText(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                            newBook.CloseParagraph()
                            newBook.insertTab()
                            newBook.OpenParagraph()
                            ' ToDo: check if reseting string this way works or is memory leak - delete object necessary or way done is sufficient
                            newWordString = ""
                        Else
                            'unknown special char
                        End If
                    ElseIf Not easySentence And sentence.specialFormat.ContainsKey(i) Then
                        ' sentence containing specially formatted words and current word is specially formatted
                        'write string to file and reset word
                        'newBook.writeTexte(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                        newBook.writeText(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                        newBook.CloseParagraph()
                        newWordString = ""
                        'get format of special word
                        Dim specFormat As MyFormat = doc.globalFormats(sentence.specialFormat.Item(i))
                        'write special word to file
                        newBook.OpenParagraph()
                        'newBook.writeTexte(sentence.words(i), calcHtmlOutputFont(curFormat.size), specFormat.colorCode, curFormat.font, specFormat.bold, specFormat.italic, specFormat.underlined)
                        newBook.writeText(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
                        newBook.CloseParagraph()
                        newBook.OpenParagraph()
                    Else
                        ' regular word string
                        If Not newWordString Is "" Then
                            newWordString += " "
                        End If
                        newWordString += sentence.words(i)
                    End If
                Next

            Next

            ' paragraph done -> write string and zeilenumbruch and close paragraph
            'newBook.writeTexte(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
            newBook.writeText(newWordString, calcHtmlOutputFont(curFormat.size), curFormat.colorCode, curFormat.font, curFormat.bold, curFormat.italic, curFormat.underlined)
            newBook.CloseParagraph()
            newBook.writeBlankLine()

        Next

        'finish book
        newBook.finishBook()

        newBook.zipEpub(title)

    End Sub


    '1 = 8        0-8 = 1
    '2 = 10      9-11 = 2
    '3 = 13      12 -13 = 3
    '4 = 13      14 – 16 = 4
    '5 = 18      17 – 21 = 5
    '6 = 24      22 – 30 = 6
    '7 = 36      >30 = 7
    ' Word font size to html font size calculator
    Private Function calcHtmlOutputFont(size As Integer) As Integer
        If size >= 0 And size < 9 Then
            Return 1
        ElseIf size >= 9 And size < 12 Then
            Return 2
        ElseIf size >= 12 And size < 14 Then
            Return 3
        ElseIf size >= 14 And size < 17 Then
            Return 4
        ElseIf size >= 17 And size < 22 Then
            Return 5
        ElseIf size >= 22 And size < 31 Then
            Return 6
        ElseIf size > 30 Then
            Return 7
        End If
    End Function

    ' Calculates addition to line maximum based on font size
    Private Function calcLines(fontSize As Integer) As Integer
        If fontSize >= 0 And fontSize < 9 Then
            Return 1
        ElseIf fontSize >= 9 And fontSize < 12 Then
            Return 1
        ElseIf fontSize >= 12 And fontSize < 14 Then
            Return 1
        ElseIf fontSize >= 14 And fontSize < 17 Then
            Return 1
        ElseIf fontSize >= 17 And fontSize < 22 Then
            Return 1.5
        ElseIf fontSize >= 22 And fontSize < 31 Then
            Return 1.9
        ElseIf fontSize > 30 Then
            Return 2.9
        End If
    End Function

    ' Calculates addition to line maximum based on font size
    Private Function lineLength(fontSize As Integer) As Integer
        If fontSize >= 0 And fontSize < 9 Then
            Return 95
        ElseIf fontSize >= 9 And fontSize < 12 Then
            Return 75
        ElseIf fontSize >= 12 And fontSize < 14 Then
            Return 60
        ElseIf fontSize >= 14 And fontSize < 17 Then
            Return 50
        ElseIf fontSize >= 17 And fontSize < 22 Then
            Return 38
        ElseIf fontSize >= 22 And fontSize < 31 Then
            Return 28
        ElseIf fontSize > 30 Then
            Return 19
        End If
    End Function

End Class